package com.xtaller.lazy.base;

import com.alibaba.fastjson.JSONObject;
import com.xtaller.lazy.lib.bean.JWTResult;
import com.xtaller.lazy.lib.convert.J;
import com.xtaller.lazy.lib.convert.P;
import com.xtaller.lazy.lib.convert.V;
import com.xtaller.lazy.lib.kit.JwtUtil;
import com.xtaller.lazy.model.base.Department;
import com.xtaller.lazy.model.base.Label;
import com.xtaller.lazy.model.base.User;
import com.xtaller.lazy.model.system.Authorities;
import com.xtaller.lazy.model.system.Dict;
import com.xtaller.lazy.service.base.UserService;
import io.jsonwebtoken.Claims;
import lombok.var;
import org.springframework.beans.factory.annotation.Autowired;

import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.Map;
import java.util.function.Function;
import java.util.function.Supplier;
import java.util.stream.Collectors;

/**
 * @version V1.0
 * @author: Taller
 * @date: 2019-04-02
 * @Description:
 */
public class TApi {
    @Autowired public HttpServletRequest request;
    @Autowired private UserService userService;

    public final String CHECK = "check";
    public final String MESSAGE = "message";
    public P print = new P(this.getClass());

    public Function<String, String> header = key -> request.getHeader(key);
    public Supplier<String> token = () -> header.apply("token");
    public Supplier<Map> subject = () -> getSubjectByKey(token.get());
    public Supplier<Long> userId = () -> {
        var map = subject.get();
        if(map == null) {
            return 0L;
        }
        return Long.parseLong(map.get("userId").toString());
    };

    /**
     * 获取url下的参数 ?后的
     */
    public Function<String, Integer> paramInt = key -> {
        var val = header.apply(key);
        return Integer.parseInt(val == null ? "0" : val);
    };
    public Function<String, Long> paramLong = key -> {
        var val = header.apply(key);
        return Long.parseLong(val == null ? "0" : val);
    };
    public Function<String, String> paramStr = key -> {
        var val = request.getParameter(key);
        return val == null ? "" : val;
    };


    /**
     * 读取token中的数据
     * */
    private Map getSubjectByKey(String key) {
        JWTResult jwt = JwtUtil.validateJWT(key);
        if (jwt.isSuccess()) {
            try {
                Claims claims = jwt.getClaims();
                String subject = claims.getSubject();
                if (V.isEmpty(subject)) {
                    return null;
                }
                return J.s2m(subject);
            } catch (Exception ex) {
                return null;
            }
        } else {
            return null;
        }
    }

    /**
     * 将page<T>转成layui的table的数据格式
     * */
    public JSONObject p2t(Object object) {
        var tem = J.o2j(object);
        var r = new JSONObject();
        r.put("code", 0);
        r.put("message", "读取成功");
        r.put("index", tem.getInteger("current") == null ? 1 : tem.getInteger("current"));
        r.put("limit", tem.getInteger("size") == null ? 0 : tem.getInteger("size"));
        r.put("count", tem.getInteger("total") == null ? 0 : tem.getInteger("total"));
        r.put("pages", tem.getInteger("pages") == null ? 1 : tem.getInteger("pages"));

        r.put("data", tem.get("records") == null ? tem.get("result") : tem.get("records"));
        return r;
    }

    /**
     * 用户数据处理
     * */
    public JSONObject formatUser(User user) {
        return J.create("niceName", user.getNickName())
                .put("loginName", user.getLoginName())
                .put("trueName", user.getTrueName())
                .put("sex", user.getSex())
                .put("phone", user.getPhone())
                .put("avatar", user.getAvatar());
    }

    /**
     * 获取权限父级数据
     * */
    public List<Authorities> getAuthByParentId(List<Authorities> auths, Long id, int isMenu){
        return auths.stream()
                .filter(x -> x.getParentId().equals(id))
                .filter(x -> x.getIsMenu() == isMenu)
                .collect(Collectors.toList());
    }

    /**
     * 给权限排序
     * */
    public class AuthoritiesTypeComparetor implements Comparator<Authorities> {
        @Override
        public int compare(Authorities h1, Authorities h2) {
            if (h1.getType() > h2.getType()) {
                return 1;
            } else if (h1.getType() == h2.getType()) {
                return 0;
            } else {
                return -1;
            }
        }
    }
    public class AuthoritiesOrderNumberComparetor implements Comparator<Authorities> {
        @Override
        public int compare(Authorities h1, Authorities h2) {
            if (h1.getOrderNumber() < h2.getOrderNumber()) {
                return 1;
            } else if (h1.getOrderNumber() == h2.getOrderNumber()) {
                return 0;
            } else {
                return -1;
            }
        }
    }

    /**
     * 格式化创建者数据
     * */
    public List<JSONObject> f2c(List<JSONObject> data){
        var uids = data.stream()
                .map(x -> x.getLong("createId"))
                .distinct()
                .collect(Collectors.toList());
        if(uids.size() == 0){
            return data;
        }
        var users = getCreator(uids);
        if(users.size() > 0){
            data.stream().forEach(x -> {
                var us = users.stream()
                        .filter(y -> y.getLong("id").equals(x.getLong("createId")))
                        .collect(Collectors.toList());
                if(us.size() > 0){
                    x.put("user", us.get(0));
                }
            });
        }
        return data;
    }

    /**
     * 通过id获取用户信息
     * */
    private List<JSONObject> getCreator(List<Long> uids){
        var users = userService.listByIds(uids);
        var list = J.list();
        if(users.size() > 0){
            users.stream().forEach(x -> {
                list.add(J.create("id", x.getId())
                        .put("loginName", x.getLoginName()));
            });
        }
        return list;
    }

    /**
     * 格式化部门为dtree插件的数据格式
     * */
    public List<JSONObject> formatDept(List<Department> depts){
        var list = J.list();
        for(var dept:depts){
            var obj = J.create("id", dept.getId())
                    .put("parentId", dept.getParentId())
                    .put("orderNumber", dept.getOrderNumber())
                    .put("title", dept.getFullName());
            list.add(obj);
        }
        return list;
    }

    /**
     * 格式化数据字典为dtree插件的数据格式
     * */
    public List<JSONObject> formatDict(List<Dict> dicts){
        var list = J.list();
        for(var dict:dicts){
            var obj = J.create("id", dict.getId())
                    .put("parentId", dict.getParentId())
                    .put("orderNumber", dict.getOrderNumber())
                    .put("title", dict.getName())
                    .put("shortName", dict.getShortName())
                    .put("py", dict.getPy())
                    .put("code", dict.getCode())
                    .put("remark", dict.getRemark());
            list.add(obj);
        }
        return list;
    }

    /**
     * 格式化画像标签为dtree插件的数据格式
     * */
    public List<JSONObject> formatLabel(List<Label> labels){
        var list = J.list();
        for(var label:labels){
            var obj = J.create("id", label.getId())
                    .put("parentId", label.getParentId())
                    .put("orderNumber", label.getOrderNumber())
                    .put("title", label.getName())
                    .put("code", label.getCode())
                    .put("dictCode", label.getDictCode())
                    .put("state", label.getState())
                    .put("type", label.getType())
                    .put("remark", label.getRemark());
            list.add(obj);
        }
        return list;
    }
}
